package com.feinno.urcs.group.service;

import com.feinno.cpim.CpimHeader;
import com.feinno.cpim.CpimMessage;
import com.feinno.urcs.content.MimeType;
import com.feinno.urcs.dns.EnumService;
import com.feinno.urcs.group.GroupConfiguration;
import com.feinno.urcs.group.api.AndPcUpGroupMsgService;
import com.feinno.urcs.group.api.GroupChatService;
import com.feinno.urcs.group.api.GroupService;
import com.feinno.urcs.group.api.GroupTerminalService;
import com.feinno.urcs.group.entity.GroupFileInfo;
import com.feinno.urcs.group.entity.GroupIndex;
import com.feinno.urcs.group.entity.GroupMessageType;
import com.feinno.urcs.group.pctask.task.AndPcGroupMsgArgs;
import com.feinno.urcs.group.pctask.task.AndPcGroupSmsArgs;
import com.feinno.urcs.group.pctask.task.AndPcGroupTextMsgArgs;
import com.feinno.urcs.group.util.CpimUtils;
import com.feinno.urcs.group.util.FileDownloadHttpClient;
import com.feinno.urcs.profile.entity.ClientType;
import com.feinno.urcs.sip.UrcsSipFactory;
import com.feinno.urcs.storage.FileStream;
import com.feinno.urcs.storage.FileStreamService;
import com.feinno.urcs.types.MobileNo;
import org.helium.framework.annotations.ServiceImplementation;
import org.helium.framework.annotations.ServiceSetter;
import org.helium.framework.rpc.LegacyRpcService;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;

import javax.sip.address.SipURI;
import java.io.IOException;
import java.text.ParseException;
import java.util.Base64;

/**
 * Created by honghao on 7/13/15.
 */
@ServiceImplementation
@LegacyRpcService(serviceName = "AndPcUpGroupMsgService")
public class AndPcUpGroupMsgServiceImpl implements AndPcUpGroupMsgService {

	private static final Logger LOGGER = LoggerFactory.getLogger(AndPcUpGroupMsgServiceImpl.class);

	@ServiceSetter
	private GroupService groupService;

	@ServiceSetter
	private EnumService enumService;

	@ServiceSetter
	private GroupTerminalService groupTerminalService;

	@ServiceSetter
	private GroupChatService groupChatService;

	@ServiceSetter
	private FileStreamService fileStreamService;

	@Override
	public void receiveGroupTextMsg(AndPcGroupTextMsgArgs args) throws Exception {
		LOGGER.info(String.format("receive Group UP Message, args :%s", args.toString()));
		try {
			GroupIndex index = groupService.getGroupIndex(args.getGroupId());
			SipURI groupUri = UrcsSipFactory.getAddressFactory().createSipURI(GroupConfiguration.INSTANCE.getGroupPrefix() + index.getGroupId(), GroupConfiguration.INSTANCE.getGroupDomain());
			CpimMessage cpim = null;
			switch (args.getMessageType()) {
				case TEXT:
					cpim = CpimUtils.createCpim(args.getUeContent(), args.getSender(), groupUri, "text/plain;charset=UTF-8", true, args.getSendTime());
					break;
				case CLOUDFILE:
					// 彩云文件共享
					cpim = CpimUtils.createCpim(args.getUeContent(), args.getSender(), groupUri, "application/cloudfile+xml", true, args.getSendTime());
					break;
				case OUTCE:
					// 表情商店
					cpim = CpimUtils.createCpim(args.getUeContent(), args.getSender(), groupUri, "application/vemoticon+xml", true, args.getSendTime());
					break;
				case LOCATION:
					// 表情商店
					cpim = CpimUtils.createCpim(args.getUeContent(), args.getSender(), groupUri, "application/vnd.gsma.rcspushlocation+xml", true, args.getSendTime());
					break;
				default:
					throw new UnsupportedOperationException("unsupport type :" + args.getMessageType().getType());

			}
			groupChatService.sendText(index.getGroupId(), args.getSender(), "message/cpim", cpim.getByteArray(), ClientType.PC, args.getGroupAtMembers(), args.getSendTime());
		} catch (Exception e) {
			LOGGER.info(String.format("receive Group UP Message,createCpim or send Error args :%s", args.toString()), e);

		}
	}

	@Override
	public void receiveGroupRichMsg(AndPcGroupMsgArgs args) throws Exception {
		try {
			LOGGER.info("receiveGroupRichMsg args : {}", args.toJsonObject());
			GroupFileInfo fileInfo = new GroupFileInfo();
			fileInfo.setSendonly(true);
			fileInfo.setRecvonly(false);
			fileInfo.setFileName(args.getFileName());
			fileInfo.setFileSize(args.getFileSize());
			fileInfo.setFileRangeEnd(args.getFileSize());
			fileInfo.setAtMembers(args.getGroupAtMembers());
			switch (args.getContentType()) {
				case IMG:
					// download picture from pc server’s ncfp
					byte[] img = FileDownloadHttpClient.getFile(args.getUrl());
					// upload to urcs server
					FileStream imgStream = uploadFile(img, args.getFileName(), args.getFileType());
					fileInfo.setFileType(args.getFileType());
					fileInfo.setAcceptType(args.getFileType());
//					fileInfo.setContent(img);
					fileInfo.setThumbnail(args.getContent());
					fileInfo.setMessageType(GroupMessageType.FILE);
					fileInfo.setPcMessageType(args.getContentType());
					fileInfo.setTransferId(imgStream.getFileId());
					break;
				case LOCATION:
//					fileInfo.setFileType("application/vnd.gsma.rcspushlocation+xml");
//					fileInfo.setAcceptType("application/vnd.gsma.rcspushlocation+xml");
//					FileStream location = uploadFile(args.getContent(), "location.xml", "application/vnd.gsma.rcspushlocation+xml");
////					fileInfo.setContent(args.getContent());
//					fileInfo.setMessageType(GroupMessageType.LOCATION);
//					fileInfo.setStatusReport(null); // TODO
//					fileInfo.setPcMessageType(args.getContentType());
////					fileInfo.setTransferId(UUID.randomUUID().toString());
//					fileInfo.setTransferId(location.getFileId());
//					fileInfo.setFileName("location.xml");
//					fileInfo.setFileSize(args.getContent().length);
					GroupIndex index = groupService.getGroupIndex(args.getGroupId());
					SipURI groupUri = UrcsSipFactory.getAddressFactory().createSipURI(GroupConfiguration.INSTANCE.getGroupPrefix() + index.getGroupId(), GroupConfiguration.INSTANCE.getGroupDomain());
					CpimMessage cpim = CpimUtils.createCpim(args.getContent(), args.getSender(), groupUri, "application/vnd.gsma.rcspushlocation+xml", true, args.getSendTime());
					groupChatService.sendText(index.getGroupId(), args.getSender(), "message/cpim", cpim.getByteArray(), ClientType.PC, args.getGroupAtMembers(), args.getSendTime());
					break;
				case CARD:
					fileInfo.setFileName("VCARD.vcf");
					fileInfo.setFileType(MimeType.VCard.getValue());
					fileInfo.setAcceptType(MimeType.VCard.getValue());
					fileInfo.setMessageType(GroupMessageType.CARD);
					fileInfo.setContent(args.getContent());
					fileInfo.setFileSize(args.getContent().length);
					fileInfo.setPcMessageType(args.getContentType());
					FileStream cardStream = uploadFile(args.getContent(), fileInfo.getFileName(), MimeType.VCard.getValue());
					fileInfo.setTransferId(cardStream.getFileId());
					break;
				case AUDIO:
					// download picture from pc server’s ncfp
					byte[] audio = FileDownloadHttpClient.getFile(args.getUrl());
					// upload to urcs server
					FileStream audioStream = uploadFile(audio, args.getFileName(), args.getFileType());
					fileInfo.setFileType(MimeType.AppOctStream.getValue());
//					fileInfo.setTimelen(args.getTimeLen() * 1000);
					fileInfo.setTimelen(args.getTimeLen());
					fileInfo.setAcceptType(MimeType.AppOctStream.getValue());
					fileInfo.setContent(audio);
					fileInfo.setPcMessageType(args.getContentType());
					fileInfo.setMessageType(GroupMessageType.FILE);
					fileInfo.setTransferId(audioStream.getFileId());
					break;
				case VIDEO:
					// download picture from pc server’s ncfp
					byte[] video = FileDownloadHttpClient.getFile(args.getUrl() + "&range=0-" + args.getFileSize());
					// upload to urcs server
					FileStream videoStream = uploadFile(video, args.getFileName(), args.getFileType());
					fileInfo.setFileType(MimeType.AppOctStream.getValue());
					fileInfo.setAcceptType(MimeType.AppOctStream.getValue());
					fileInfo.setMessageType(GroupMessageType.FILE);
					fileInfo.setContent(video);
					fileInfo.setPcMessageType(args.getContentType());
					fileInfo.setThumbnail(args.getContent());
					fileInfo.setTransferId(videoStream.getFileId());
					break;
				default:
					throw new UnsupportedOperationException("unsupport type :" + args.getContentType().getType());
			}
			fileInfo.setIsPc(true);
			LOGGER.info("receiveGroupRichMsg fileinfo to json :{}", fileInfo.toJsonObject());
			groupChatService.sendFile(args.getGroupId(), args.getSender(), fileInfo, args.getSendTime());
		} catch (Exception e) {
			LOGGER.error("receiveGroupRichMsg from pc server occur error :{}", e);
			throw e;
		}
	}

	@Override
	public void sendGroupSms(AndPcGroupSmsArgs args) throws Exception {
		groupChatService.sendSms(args.getSender(), args.getGroupId(), args.getContent());
	}

	private FileStream uploadFile(byte[] buffer, String fileName, String fileType) throws IOException {
		FileStream fileStream = fileStreamService.create();
		fileStream.getOutputSteam().write(buffer);
		fileStream.setFileType(fileType);
		fileStream.setFileSize(buffer.length);
		fileStream.setFileName(fileName);
		fileStream.flush();
		return fileStream;
	}
}
